<template>
  <el-dialog
    :close-on-click-modal="false"
    :title="title"
    :visible.sync="show"
    :append-to-body="true"
    top="10px"
    custom-class="map-fence-dialog"
    width="1200px"
  >
    <div id="fenceMap">
      <div class="map-draw-controls">
        <el-radio-group
          v-model="form.fenceType"
          @change="startDraw"
          size="small"
        >
          <el-radio-button label="circle"
            ><i class="iconfont el-icon-circle"> </i
            ><span>圆形</span></el-radio-button
          >
          <el-radio-button label="rectangle"
            ><i class="iconfont el-icon-rectangle"> </i
            ><span>矩形</span></el-radio-button
          >
          <el-radio-button label="polygon"
            ><i class="iconfont el-icon-polygon"> </i
            ><span>多边形</span></el-radio-button
          >
        </el-radio-group>
        <el-button
          type="primary"
          @click="startDrawPath"
          plain
          icon="el-icon-edit"
          size="small"
          >绘制检查点</el-button
        >
      </div>
      <!-- 输入框自动完成组件 -->
      <el-autocomplete
        v-model="searchText"
        :maxlength="200"
        :fetch-suggestions="onSearchResult"
        :trigger-on-focus="false"
        placeholder="请搜索或选择地点"
        @select="handleSelect"
        popper-class="dailog-addressbox-list"
        suffix-icon="el-icon-search"
        class="search-box"
        clearable
      >
        <template slot-scope="{ item }">
          <span class="name">{{ item.name }}</span>
          <!-- <span class="addr">{{ item.district }}</span> -->
        </template>
      </el-autocomplete>
    </div>
    <div slot="footer" class="dialog-footer">
      <el-alert
        title="1.默认围栏为浅蓝色 可通过选择围栏背景色更改围栏颜色"
        type="info"
        :closable="false"
        style="width: 100%; float: left"
      >
      </el-alert>
      <el-alert
        title="2.绘制围栏鼠标左键绘制点，鼠标右键完成绘制"
        type="info"
        :closable="false"
        style="width: 100%; float: left"
      >
      </el-alert>
      <el-alert
        title="3. 有需要可以点击绘制检查点绘制巡检工作路线"
        type="info"
        :closable="false"
        style="width: 100%; float: left"
      >
      </el-alert>
      <el-form
        ref="form"
        :model="form"
        :rules="rules"
        label-width="110px"
        style="margin-top: 15px"
      >
        <el-row>
          <el-col :span="10">
            <el-form-item label="所属部门单位" prop="deptId">
              <treeselect
                v-model="form.deptId"
                :options="deptOptions"
                :disable-branch-nodes="false"
                :show-count="true"
                placeholder="请选择归属部门"
                :defaultExpandLevel="2"
              />
            </el-form-item>

            <!-- <el-form-item label="半径（米）" v-if="form.fenceType == 1">
              <el-input
                v-model="form.radius"
                placeholder="在地图上绘制获得"
                :readonly="true"
              />
            </el-form-item> -->
          </el-col>
          <el-col :span="10">
            <el-form-item label="围栏名称" prop="fenceName">
              <el-input v-model="form.fenceName" />
            </el-form-item>
          </el-col>

          <!-- <el-form-item label="坐标点" prop="latlng">
              <el-input
                v-model="form.latlng"
                placeholder="在地图上绘制获得"
                :readonly="true"
              >
              </el-input>
            </el-form-item>

            <el-form-item label="检查点坐标点" prop="checkPoints">
              <el-input v-model="form.checkPoints" placeholder="请输入内容" />
            </el-form-item> -->

          <el-col :span="4">
            <el-form-item label="围栏背景色" prop="bgColor">
              <el-color-picker
                v-model="form.bgColor"
                show-alpha
              ></el-color-picker>
            </el-form-item>
          </el-col>
        </el-row>
        <el-row>
          <el-form-item label="检查点名称" prop="checkNames">
            <div style="display: flex; align-items: flex-start">
              <div
                style="
                  padding: 2px;
                  border: 1px solid #c0c4cc;
                  border-radius: 4px;
                  width: 374px;
                  height: 70px;
                  margin-right: 30px;
                  overflow-y: auto;
                "
              >
                <el-tag
                  v-for="(way, index) in form.checkNames"
                  :key="index"
                  style="margin-right: 3px"
                  closable
                  @close="handleRemoveCheckPoint(index)"
                  >{{ way }}</el-tag
                >
              </div>
              <el-input
                v-model="checkName"
                placeholder="请输入检查点名称"
                style="width: 200px"
              >
                <el-button
                  slot="append"
                  icon="el-icon-plus"
                  @click="addCheckPoint"
                ></el-button
              ></el-input>
            </div>
          </el-form-item>
        </el-row>
      </el-form>
      <el-button @click="closeDialog"> 取消 </el-button>
      <el-button type="primary" @click="handleSaveFence"> 确定 </el-button>
    </div>
  </el-dialog>
</template>

<script>
import AMap from "AMap";
let mouseTool = null;

import { addFence, updateFence } from "@/api/base/fence";

import Treeselect from "@riophae/vue-treeselect";
import "@riophae/vue-treeselect/dist/vue-treeselect.css";
export default {
  name: "fenceMap",
  components: {
    Treeselect,
  },
  props: {
    visible: {
      required: true,
      default: false,
    },
    fenceObj: {
      type: Object,
      default: {},
    },
    deptOptions: {
      type: Array,
      default: [],
    },
  },
  data() {
    return {
      map: null,
      searchText: "",
      title: "",
      form: {},
      isStartDrawPath: false, //是否开始绘制检查点
      // 表单校验
      rules: {
        fenceId: [
          { required: true, message: "围栏id不能为空", trigger: "blur" },
        ],
        deptId: [
          { required: true, message: "部门id不能为空", trigger: "blur" },
        ],
        fenceName: [
          { required: true, message: "围栏名称不能为空", trigger: "blur" },
        ],
        fenceType: [
          {
            required: true,
            message: "围栏类型 字典不能为空",
            trigger: "change",
          },
        ],
        latlng: [
          { required: true, message: "经纬度合集不能为空", trigger: "blur" },
        ],
        checkNames: [
          { required: false, message: "检查点名必填", trigger: "blur" },
        ],
      },
      checkName: "",
    };
  },
  computed: {
    show: {
      get() {
        return this.visible;
      },
      set(val) {
        this.$emit("update:visible", val);
      },
    },
  },
  watch: {
    show: function (val) {
      if (val) {
        this.form = JSON.parse(JSON.stringify(this.fenceObj));
        if (!this.map) {
          this.$nextTick(function () {
            this.mapInit();
          });
        } else {
          this.showFence();
        }
      }
    },
  },
  methods: {
    closeDialog() {
      //当面板关闭(点击关闭按钮)
      this.show = false;
    },
    onSearchResult(pois, cb) {
      let self = this;
      let searchkey = this.searchText;
      AMap.plugin(["AMap.Autocomplete"], function () {
        var autoOptions = {
          city: "", // 城市，默认全国
        };
        var autoComplete = new AMap.Autocomplete(autoOptions);
        autoComplete.search(searchkey, function (status, result) {
          // 搜索成功时，result即是对应的匹配数据
          if (result && result.tips) {
            let results = result.tips;
            if (results) {
              cb(results);
            } else {
              //搜索无结果
              cb("");
            }
          }
        });
      });
    },
    handleSelect(item) {
      // this.searchText = item.name + item.district;
      this.searchText = item.name;
      let self = this;
      if (item.location == "") {
        let placemap = new AMap.Geocoder({
          radius: 1000,
          extensions: "all",
        });
        placemap.getLocation(this.searchText, function (status, result) {
          if (status === "complete" && result.info === "OK") {
            self.setSearchPos(result.geocodes[0].location);
          }
        });
      } else {
        self.setSearchPos(item.location);
      }
    },
    setSearchPos(posi) {
      this.map.setZoomAndCenter(15, [posi.lng, posi.lat]);
    },
    initCircleEditor(drawObj) {
      let self = this;
      //构造圆形编辑对象，并开启圆形的编辑状态
      this.map.plugin(["AMap.CircleEditor"], function () {
        let circleEditor = new AMap.CircleEditor(self.map, drawObj);
        circleEditor.open();
      });
    },
    initRectangleEditor(drawObj) {
      let self = this;
      //构造矩形编辑对象，并开启矩形的编辑状态
      this.map.plugin(["AMap.RectangleEditor"], function () {
        let rectangleEditor = new AMap.RectangleEditor(self.map, drawObj);
        rectangleEditor.open();
      });
    },
    initPolyEditor(drawObj) {
      let self = this;
      //构造多边形和折线编辑对象，并开启矩形的编辑状态
      this.map.plugin(["AMap.PolyEditor"], function () {
        let polylineEditor = new AMap.PolyEditor(self.map, drawObj);
        polylineEditor.open();
      });
    },
    mapInit() {
      this.map = new AMap.Map("fenceMap", {
        resizeEnable: true,
        zoom: 12,
        zooms: [3, 20],
        expandZoomRange: true,
        mapStyle: "amap://styles/fresh",
      });
      let self = this;
      this.map.plugin(["AMap.MouseTool"], function () {
        //鼠标工具插件
        mouseTool = new AMap.MouseTool(self.map);
      });
      this.showFence();

      AMap.event.addListener(mouseTool, "draw", function (event) {
        // event.obj 为绘制出来的覆盖物对象
        let drawObj = event.obj;
        if (!self.isStartDrawPath) {
          if (self.form.fenceType == "circle") {
            //圆形
            self.initCircleEditor(drawObj);
          } else if (self.form.fenceType == "rectangle") {
            //矩形
            var rectangleBounds = drawObj.getBounds();
            // var southWest = new AMap.LngLat(
            //   rectangleBounds.southwest.lng,
            //   rectangleBounds.southwest.lat
            // );
            // var northEast = new AMap.LngLat(
            //   rectangleBounds.northeast.lat,
            //   rectangleBounds.northeast.lat
            // );

            // var bounds = new AMap.Bounds(southWest, northEast);

            console.log(drawObj.getBounds());
            self.map.clearMap();
            var rectangle = new AMap.Rectangle({
              bounds: rectangleBounds,
              strokeColor: "red",
              strokeWeight: 6,
              strokeOpacity: 0.5,
              strokeDasharray: [30, 10],
              // strokeStyle还支持 solid
              strokeStyle: "solid",
              fillColor: self.form.bgColor,
              fillOpacity: 1,
              cursor: "pointer",
              zIndex: 50,
              map: self.map,
            });
            self.initRectangleEditor(rectangle);
          } else if (self.form.fenceType == "polygon") {
            //多边形
            self.initPolyEditor(drawObj);
          }
        }

        mouseTool.close(false);

        self.$message.info("绘制完成");
      });
    },
    startDraw(type) {
      this.isStartDrawPath = false;
      this.form.fenceType = type;
      this.map.clearMap();
      let infoMsg = "";
      if (type == "circle") {
        //圆形
        infoMsg = "点击鼠标左键确定中心点，移动确定半径，松开鼠标完成";
        mouseTool.circle({
          strokeColor: "red",
          strokeOpacity: 0.2,
          strokeWeight: 4,
          fillColor: this.form.bgColor,
          fillOpacity: 1,
          strokeStyle: "solid",
          // 线样式还支持 'dashed'
          // strokeDasharray: [30,10],
        });
      } else if (type == "rectangle") {
        //矩形
        infoMsg = "点击鼠标左键确定左上角，松开鼠标完成确定矩形右下角";
        mouseTool.rectangle({
          strokeColor: "red",
          strokeOpacity: 0.2,
          strokeWeight: 4,
          fillColor: this.form.bgColor,
          fillOpacity: 1,
          strokeStyle: "solid",
          // strokeDasharray: [30,10],
        });
      } else if (type == "polygon") {
        //多边形
        infoMsg = "点击鼠标左键确定多边形的角，右键完成绘制";
        mouseTool.polygon({
          strokeColor: "red",
          strokeOpacity: 0.2,
          strokeWeight: 4,
          fillColor: this.form.bgColor,
          fillOpacity: 1,
          strokeStyle: "solid",
        });
      }
    },
    startDrawPath() {
      this.isStartDrawPath = true;
      if (this.map.getAllOverlays("polyline")) {
        this.map.remove(this.map.getAllOverlays("polyline"));
      }
      //路线
      mouseTool.polyline({
        strokeColor: "#3366FF",
        strokeOpacity: 1,
        strokeWeight: 4,
        // 线样式还支持 'dashed'
        strokeStyle: "solid",
        // strokeStyle是dashed时有效
        // strokeDasharray: [10, 5],
      });
      this.$message.info("点击鼠标反键完成绘制");
    },
    showFence() {
      this.map.clearMap();
      if (this.form.fenceId) {
        this.title = "修改网格";

        if (this.form.fenceType == "circle") {
          // 构造矢量圆形
          let circlePoints = this.form.latlng.split(",");
          var circle = new AMap.Circle({
            center: new AMap.LngLat(circlePoints[1], circlePoints[0]), // 圆心位置
            radius: this.form.radius, //半径
            strokeColor: "red",
            strokeOpacity: 0.2,
            strokeWeight: 4,
            fillColor: this.form.bgColor,
            fillOpacity: 1,
            strokeStyle: "solid",
          });
          this.map.add(circle);
          this.map.setFitView();
          this.initCircleEditor(circle);
        } else if (this.form.fenceType == "rectangle") {
          let recPoints = this.form.latlng.split("|");

          // 构造矢量矩形  数据库存储的是左上和右下
          var southWest = new AMap.LngLat(
            recPoints[0].split(",")[1],
            recPoints[0].split(",")[0]
          );
          var northEast = new AMap.LngLat(
            recPoints[1].split(",")[1],
            recPoints[1].split(",")[0]
          );

          var bounds = new AMap.Bounds(southWest, northEast);

          var rectangle = new AMap.Rectangle({
            bounds: bounds,
            strokeColor: "red",
            strokeOpacity: 0.2,
            strokeWeight: 4,
            fillColor: this.form.bgColor,
            fillOpacity: 1,
            strokeStyle: "solid",
          });
          this.map.add(rectangle);
          this.map.setFitView();
          this.initRectangleEditor(rectangle);
        } else if (this.form.fenceType == "polygon") {
          // 构造矢量多边形
          let polyPoints = this.form.latlng.split("|");
          let path = [];
          polyPoints.forEach((poly) => {
            let item = poly.split(",");
            path.push([item[1], item[0]]);
          });

          var polygon = new AMap.Polygon({
            path: path,
            strokeColor: "red",
            strokeOpacity: 0.2,
            strokeWeight: 4,
            fillColor: this.form.bgColor,
            fillOpacity: 1,
            strokeStyle: "solid",
          });

          this.map.add(polygon);
          this.map.setFitView();
          this.initPolyEditor(polygon);
        }

        if (this.form.checkPoints) {
          let polylinePoints = this.form.checkPoints.split("|");
          let path = [];
          polylinePoints.forEach((poly) => {
            let item = poly.split(",");
            path.push([item[1], item[0]]);
          });
          //构造路线
          var polyline = new AMap.Polyline({
            strokeColor: "#3366FF",
            path: path,

            strokeOpacity: 1,
            strokeWeight: 4,
            // 线样式还支持 'dashed'
            strokeStyle: "solid",
            // strokeStyle是dashed时有效
            // strokeDasharray: [10, 5],
          });
          this.map.add(polyline);
          this.map.setFitView();
        }
      } else {
        this.title = "新增网格";
      }
    },
    handleSaveFence() {
      let flagHasDraw = false;
      let newpoints = [];
      if (this.form.fenceType == "circle") {
        //圆形

        if (this.map.getAllOverlays("circle").length > 0) {
          let drawObj = this.map.getAllOverlays("circle")[0];
          let centerPoint = drawObj.getCenter();
          newpoints = [[centerPoint.lat, centerPoint.lng]];
          this.form.radius = drawObj.getRadius();
          flagHasDraw = true;
        }
      } else if (this.form.fenceType == "rectangle") {
        //矩形

        if (this.map.getAllOverlays("rectangle").length > 0) {
          let drawObj = this.map.getAllOverlays("rectangle")[0];
          var southWest = drawObj.getBounds().getSouthWest();
          var northEast = drawObj.getBounds().getNorthEast();

          newpoints = [
            [southWest.lat, southWest.lng],
            [northEast.lat, northEast.lng],
          ];

          this.form.radius = "";
          flagHasDraw = true;
        }
      } else if (this.form.fenceType == "polygon") {
        //多边形

        if (this.map.getAllOverlays("polygon").length > 0) {
          let drawObj = this.map.getAllOverlays("polygon")[0];

          let points = drawObj.getPath();

          points.forEach((item) => {
            newpoints.push([item.lat, item.lng]);
          });
          this.form.radius = "";
          flagHasDraw = true;
        }
      }
      //折线
      if (this.map.getAllOverlays("polyline").length > 0) {
        let drawPath = this.map.getAllOverlays("polyline")[0];
        let pathPoints = drawPath.getPath();
        let pathCheckPoints = [];
        pathPoints.forEach((item) => {
          pathCheckPoints.push([item.lat, item.lng]);
        });
        if (this.form.checkNames.length != pathCheckPoints.length) {
          this.$modal.msgError("请保持检查点的名称数量与检查点位置数量一致");
          return;
        }
        this.form.checkPoints = pathCheckPoints.join("|");
        this.rules.checkNames[0].required = true;
      } else {
        this.form.checkPoints = "";
        this.rules.checkNames[0].required = false;
      }

      this.form.latlng = newpoints.join("|");
      if (flagHasDraw) {
        this.submitForm();
      } else {
        this.$modal.msgError("请在地图上绘制网格");
      }
    },
    /** 提交按钮 */
    submitForm() {
      this.$refs["form"].validate((valid) => {
        if (valid) {
          this.buttonLoading = true;
          let params = JSON.parse(JSON.stringify(this.form));

          params.checkNames = params.checkNames.join(",");

          if (this.form.fenceId != null) {
            updateFence(params)
              .then((response) => {
                this.$modal.msgSuccess("修改成功");
                this.$emit("refreshList");
                this.show = false;
              })
              .finally(() => {
                this.buttonLoading = false;
              });
          } else {
            addFence(params)
              .then((response) => {
                this.$modal.msgSuccess("新增成功");
                this.$emit("refreshList");
                this.show = false;
              })
              .finally(() => {
                this.buttonLoading = false;
              });
          }
        }
      });
    },
    addCheckPoint() {
      if (this.checkName) {
        this.form.checkNames.push(this.checkName);
        this.checkName = "";
      }
    },
    handleRemoveCheckPoint(index) {
      this.form.checkNames.splice(index, 1);
    },
  },
};
</script>

<style lang="scss">
.map-fence-dialog {
  .el-dialog__body {
    padding: 0 20px;
  }
}
#fenceMap {
  width: 100%;
  height: 600px;
  .map-draw-controls {
    position: absolute;
    z-index: 999;
  }
  div {
    &.el-input {
      &:hover {
        span.el-input__suffix {
          .el-icon-search {
            visibility: hidden;
            transition: all 0s;
          }
        }
      }
      input {
        color: #fff;
      }
    }
  }

  .search-box {
    width: 300px;
    position: absolute !important;
    margin-left: 50%;
    transform: translateX(-50%);
    margin-top: 10px;
    z-index: 5;
    .el-input__suffix {
      color: #50e3c2;
    }
    .el-input__inner {
      background: rgba(0, 0, 0, 0.7);
    }
  }
}
</style>
